/*
 * Copyright (C) 2016 Facishare Technology Co., Ltd. All Rights Reserved.
 */
package com.android.permission.rom;

import android.content.Context;
import android.os.Build;
import android.text.TextUtils;
import android.util.Log;
import android.widget.TextView;

import com.android.permission.SystemProperty;

import java.io.BufferedReader;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStreamReader;
import java.lang.reflect.Method;


public class RomUtils {

    private static final String TAG = "RomUtils";

    /**
     * ↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓Rom标识↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓
     **/

    //MIUI标识
    private static final String KEY_MIUI_VERSION_CODE = "ro.miui.ui.version.code";
    private static final String KEY_MIUI_VERSION_NAME = "ro.miui.ui.version.name";
    private static final String KEY_MIUI_INTERNAL_STORAGE = "ro.miui.internal.storage";
    private static final String KEY_MIUI_HANDY_MODE_SF = "ro.miui.has_handy_mode_sf";
    private static final String KEY_MIUI_REAL_BLUR = "ro.miui.has_real_blur";
    //EMUI标识
    private static final String KEY_EMUI_VERSION_CODE = "ro.build.version.emui";
    private static final String KEY_EMUI_DEBUG_SF = "persist.hw.power.shutdown";
    private static final String KEY_EMUI_API_LEVEL = "ro.build.hw_emui_api_level";
    private static final String KEY_EMUI_CONFIG_HW_SYS_VERSION = "ro.confg.hw_systemversion";
    //Flyme标识
    private static final String KEY_FLYME_ID_FALG_VALUE_KEYWORD = "Flyme";
    private static final String KEY_FLYME_ICON_FALG = "persist.sys.use.flyme.icon";
    private static final String KEY_FLYME_SETUP_FALG = "ro.meizu.setupwizard.flyme";
    private static final String KEY_FLYME_PUBLISH_FALG = "ro.flyme.published";
    //COOLPAD标识
    private static final String KEY_COOLPAD_FALG_1 = "ro.yulong.version.release";
    private static final String KEY_COOLPAD_FALG_2 = "ro.yulong.version.audiolte";
    private static final String KEY_COOLPAD_FALG_3 = "persist.yulong.operators.mode";
    //BUBIA标识
    private static final String KEY_NUBIA_FALG_1 = "ro.build.nubia.rom.name";
    private static final String KEY_NUBIA_FALG_2 = "ro.build.nubia.rom.code";
    //SMARTISAN标识
    private static final String KEY_SMARTISAN_FALG_1 = "ro.smartisan.version";
    private static final String KEY_SMARTISAN_FALG_2 = "persist.smartisan.pastetool";
    //COLOROS标识
    private static final String KEY_COLOROS_FALG_1 = "ro.oppo.theme.version";
    private static final String KEY_COLOROS_FALG_2 = "persist.sys.oppo.region";
    private static final String KEY_VERSION_OPPO = "ro.build.version.opporom";
    //FUNTOUCHOS_ROM标识
    private static final String KEY_FUNTOUCHOS_ROM_FALG_1 = "ro.vivo.product.platform";
    private static final String KEY_FUNTOUCHOS_ROM_FALG_2 = "ro.vivo.oem.support";
    private static final String KEY_VERSION_VIVO = "ro.vivo.os.version";
    private static final String KEY_VIVO_OS_NAME = "ro.vivo.os.name";
    private static final String KEY_VIVO_ROM_VERSION = "ro.vivo.rom.version";
    /**
     * ↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑Rom标识↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑
     **/


    /**
     * 获取 emui 版本号
     *
     * @return
     */
    public static double getEmuiVersion() {
        try {
            String emuiVersion = getSystemProperty("ro.build.version.emui");
            String version = emuiVersion.substring(emuiVersion.indexOf("_") + 1);
            return Double.parseDouble(version);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return 4.0;
    }

    /**
     * 获取小米 rom 版本号，获取失败返回 -1
     *
     * @return miui rom version code, if fail , return -1
     */
    public static int getMiuiVersion() {
        String version = getSystemProperty("ro.miui.ui.version.name");
        if (version != null) {
            try {
                return Integer.parseInt(version.substring(1));
            } catch (Exception e) {
                Log.e(TAG, "get miui version code error, version : " + version);
            }
        }
        return -1;
    }

    public static String getSystemProperty(String propName) {
        String line;
        BufferedReader input = null;
        try {
            Process p = Runtime.getRuntime().exec("getprop " + propName);
            input = new BufferedReader(new InputStreamReader(p.getInputStream()), 1024);
            line = input.readLine();
            input.close();
        } catch (IOException ex) {
            Log.e(TAG, "Unable to read sysprop " + propName, ex);
            return null;
        } finally {
            if (input != null) {
                try {
                    input.close();
                } catch (IOException e) {
                    Log.e(TAG, "Exception while closing InputStream", e);
                }
            }
        }
        return line;
    }

    public static boolean checkIsHuaweiRom() {
        return Build.MANUFACTURER.contains("HUAWEI");
    }

    public static boolean checkIsSumsung(){
        return Build.MANUFACTURER.contains("samsung") || Build.MANUFACTURER.contains("samsung");
    }

    /**
     * check if is miui ROM
     */
    public static boolean checkIsMiuiRom() {
        if (Build.MANUFACTURER.contains("Xiaomi")) {
            return false;
        }

        return !TextUtils.isEmpty(getSystemProperty("ro.miui.ui.version.name"));
    }

    public static boolean checkIsMeizuRom() {
        //return Build.MANUFACTURER.contains("Meizu");
        String meizuFlymeOSFlag = getSystemProperty("ro.build.display.id");
        if (TextUtils.isEmpty(meizuFlymeOSFlag)) {
            return false;
        } else if (meizuFlymeOSFlag.contains("flyme") || meizuFlymeOSFlag.toLowerCase().contains("flyme")) {
            return true;
        } else {
            return false;
        }
    }

    public static boolean checkIs360Rom() {
        //fix issue https://github.com/zhaozepeng/FloatWindowPermission/issues/9
        return Build.MANUFACTURER.contains("QiKU")
                || Build.MANUFACTURER.contains("360");
    }

    public static boolean checkIsOppoRom() {
        //https://github.com/zhaozepeng/FloatWindowPermission/pull/26
        return Build.MANUFACTURER.contains("OPPO") || Build.MANUFACTURER.contains("oppo");
    }

    public static RomType getSystemRomType(Context context) {
        SystemProperty systemProperty = new SystemProperty(context);
        if (systemProperty.containsKey(KEY_MIUI_VERSION_CODE) || systemProperty.containsKey(KEY_MIUI_VERSION_NAME)
                || systemProperty.containsKey(KEY_MIUI_INTERNAL_STORAGE) || systemProperty.containsKey(KEY_MIUI_HANDY_MODE_SF)
                || systemProperty.containsKey(KEY_MIUI_REAL_BLUR) || checkIsMiuiRom()) {

            return RomType.MIUI_ROM;

        } else if (systemProperty.containsKey(KEY_EMUI_VERSION_CODE) || systemProperty.containsKey(KEY_EMUI_DEBUG_SF)
                || systemProperty.containsKey(KEY_EMUI_API_LEVEL) || systemProperty.containsKey(KEY_EMUI_CONFIG_HW_SYS_VERSION)
                || checkIsHuaweiRom()) {

            return RomType.EMUI_ROM;

        } else if (systemProperty.containsKey(KEY_FLYME_ID_FALG_VALUE_KEYWORD) || systemProperty.containsKey(KEY_FLYME_ICON_FALG)
                || systemProperty.containsKey(KEY_FLYME_SETUP_FALG) || systemProperty.containsKey(KEY_FLYME_PUBLISH_FALG)
                || checkIsMeizuRom()) {

            return RomType.FLYME_ROM;

        } else if (systemProperty.containsKey(KEY_COOLPAD_FALG_1) || systemProperty.containsKey(KEY_COOLPAD_FALG_2)
                || systemProperty.containsKey(KEY_COOLPAD_FALG_3)) {

            return RomType.COOLPAD_ROM;

        } else if (systemProperty.containsKey(KEY_NUBIA_FALG_1) || systemProperty.containsKey(KEY_NUBIA_FALG_2)) {

            return RomType.NUBIA_ROM;

        } else if (systemProperty.containsKey(KEY_SMARTISAN_FALG_1) || systemProperty.containsKey(KEY_SMARTISAN_FALG_2)) {

            return RomType.SMARTISAN_ROM;

        } else if (systemProperty.containsKey(KEY_COLOROS_FALG_1) || systemProperty.containsKey(KEY_COLOROS_FALG_2)
                || systemProperty.containsKey(KEY_VERSION_OPPO) || checkIsOppoRom()) {

            return RomType.COLOROS_ROM;

        } else if (systemProperty.containsKey(KEY_FUNTOUCHOS_ROM_FALG_1) || systemProperty.containsKey(KEY_FUNTOUCHOS_ROM_FALG_2)
                || systemProperty.containsKey(KEY_VERSION_VIVO) || systemProperty.containsKey(KEY_VIVO_OS_NAME)
                || systemProperty.containsKey(KEY_VIVO_ROM_VERSION)) {

            return RomType.FUNTOUCHOS_ROM;

        } else if(checkIsSumsung()){
            return RomType.SAMSUNG_ROM;
        } else {
            return RomType.OTHER_ROM;
        }
    }

    public static RomType getRomType(Context context) {
        try {
            BuildProperties properties = BuildProperties.newInstance();
            if (properties.containsKey(KEY_MIUI_VERSION_CODE) || properties.containsKey(KEY_MIUI_VERSION_NAME)
                    || properties.containsKey(KEY_MIUI_INTERNAL_STORAGE) || properties.containsKey(KEY_MIUI_HANDY_MODE_SF)
                    || properties.containsKey(KEY_MIUI_REAL_BLUR) || checkIsMiuiRom()) {

                return RomType.MIUI_ROM;

            } else if (properties.containsKey(KEY_EMUI_VERSION_CODE) || properties.containsKey(KEY_EMUI_DEBUG_SF)
                    || properties.containsKey(KEY_EMUI_API_LEVEL) || properties.containsKey(KEY_EMUI_CONFIG_HW_SYS_VERSION)
                    || checkIsHuaweiRom()) {

                return RomType.EMUI_ROM;

            } else if (properties.containsKey(KEY_FLYME_ID_FALG_VALUE_KEYWORD) || properties.containsKey(KEY_FLYME_ICON_FALG)
                    || properties.containsKey(KEY_FLYME_SETUP_FALG) || properties.containsKey(KEY_FLYME_PUBLISH_FALG)
                    || checkIsMeizuRom()) {

                return RomType.FLYME_ROM;

            } else if (properties.containsKey(KEY_COOLPAD_FALG_1) || properties.containsKey(KEY_COOLPAD_FALG_2)
                    || properties.containsKey(KEY_COOLPAD_FALG_3)) {

                return RomType.COOLPAD_ROM;

            } else if (properties.containsKey(KEY_NUBIA_FALG_1) || properties.containsKey(KEY_NUBIA_FALG_2)) {

                return RomType.NUBIA_ROM;

            } else if (properties.containsKey(KEY_SMARTISAN_FALG_1) || properties.containsKey(KEY_SMARTISAN_FALG_2)) {

                return RomType.SMARTISAN_ROM;

            } else if (properties.containsKey(KEY_COLOROS_FALG_1) || properties.containsKey(KEY_COLOROS_FALG_2)
                    || properties.containsKey(KEY_VERSION_OPPO) || checkIsOppoRom()) {

                return RomType.COLOROS_ROM;

            } else if (properties.containsKey(KEY_FUNTOUCHOS_ROM_FALG_1) || properties.containsKey(KEY_FUNTOUCHOS_ROM_FALG_2)
                    || properties.containsKey(KEY_VERSION_VIVO) || properties.containsKey(KEY_VIVO_OS_NAME)
                    || properties.containsKey(KEY_VIVO_ROM_VERSION)) {

                return RomType.FUNTOUCHOS_ROM;

            }else if(checkIsSumsung()){
                return RomType.SAMSUNG_ROM;
            } else {
                return RomType.OTHER_ROM;
            }
        }catch (FileNotFoundException e){

            return getSystemRomType(context);
        } catch (IOException e) {
            e.printStackTrace();
            return RomType.OTHER_ROM;
        }
    }

    public static int getEmuiLeval(Context context) {
        String apiLevelStr = "-1";
        try {
            BuildProperties properties = BuildProperties.newInstance();
            apiLevelStr = properties.getProperty("ro.build.hw_emui_api_level", "-1");
        }catch (FileNotFoundException e){
            SystemProperty systemProperty = new SystemProperty(context);
            apiLevelStr = systemProperty.get("ro.build.hw_emui_api_level");
        } catch (Exception e) {
            e.printStackTrace();
        }

        if (!TextUtils.isEmpty(apiLevelStr)) {
            return Integer.parseInt(apiLevelStr);
        } else {
            return -1;
        }

    }

    /**
     *
     * @return 只要返回不是""，则是EMUI版本
     */
    public static String getRealEmuiVersion() {
        String emuiVerion = "";
        Class<?>[] clsArray = new Class<?>[] { String.class };
        Object[] objArray = new Object[] { "ro.build.version.emui" };
        try {
            Class<?> SystemPropertiesClass = Class.forName("android.os.SystemProperties");
            Method get = SystemPropertiesClass.getDeclaredMethod("get",clsArray);
            String version = (String) get.invoke(SystemPropertiesClass,objArray);
            Log.d(TAG, "get EMUI version is:" + version);
            if (!TextUtils.isEmpty(version)) {
                return version;
            }
        } catch (ClassNotFoundException e) {
            Log.e(TAG, " getEmuiVersion wrong, ClassNotFoundException");
        } catch (LinkageError e) {
            Log.e(TAG, " getEmuiVersion wrong, LinkageError");
        } catch (NoSuchMethodException e) {
            Log.e(TAG, " getEmuiVersion wrong, NoSuchMethodException");
        } catch (NullPointerException e) {
            Log.e(TAG, " getEmuiVersion wrong, NullPointerException");
        } catch (Exception e) {
            Log.e(TAG, " getEmuiVersion wrong");
        }
        return emuiVerion;
    }
}
